import { Vector3 } from "./Vector3";

//import { AssertUtil } from "../../common";

/**
 * 数据结构 - 集合
 * 这里应该用一种内存结构连续的二叉查找树的数据结构代替。
 *
 * @version 20190422
 * @copyright 司空科技股份有限公司
 */
export interface Set<T> {
    get(idx: number): T;
    append(t: T);
    remove(t: T): boolean;
    indexOf(t: T): number;
    insert(t: T): boolean;
    size(): number;
    clear();
    toArray(): T[];
}

export class UnorderedSet<T> implements Set<T> {
    private _arr: Array<T>;

    public constructor(size?: number) {
        var len = (size !== undefined) ? size : 0;
        this._arr = new Array<T>(len);
    }

    /**
     * 直接访问值。
     */
    public get value(): T[] {
        return this._arr;
    }

    /**
     * 集合中元素的长度。
     */
    public get length() {
        return this._arr.length;
    }

    /**
     * 索引集合某个位置的值。
     * 
     * @param idx 索引位置。
     */
    public get(idx: number): T {
        return this._arr[idx];
    }

    /**
     * 赋值函数。
     * 
     * @param set 集合。
     */
    public assign(set: UnorderedSet<T>): UnorderedSet<T> {
        this.clear();
        var len = set.length;
        for (var i = 0; i < len; i++) {
            var t = set._arr[i];
            this._arr.push(t);
        }
        return this;
    }

    /**
     * 添加一个元素到集合，如果元素存在则不添加。
     * 
     * @param t 
     * @rturn 添加前的个数。
     */
    public append(t: T): number {
        var len = this._arr.length;
        this.indexOf(t) < 0 && this._arr.push(t);
        return len;
    }

    /**
     * 移除集合中元素t。
     * 
     */
    public remove(t: T): boolean {
        var index = this.indexOf(t);
        if (index >= 0) {
            this._arr.splice(index,1);
            return true;
        }
        return false;
    }

    /**
     * 移除索引为idx的节点。
     * 
     * @param idx 索引
     */
    public removeAt(idx: number) {
        //    AssertUtil.debugTrue(idx < this.arr.length && idx>=0);
        delete this._arr[idx];
    }

    /**
     * 检索元素在集合里的索引位置。
     * 
     * @param t 元素
     * @returns 索引位置
     */
    public indexOf(t: T): number {
        var len = this._arr.length;
        for (var i = 0; i < len; i++) {
            var item = this._arr[i];
            if (t === item) {
                return i;
            }
        }
        return -1;
    }

    /**
     * 插入一个元素，若元素已经存在则返回false。
     * 
     * @param t 元素。
     */
    public insert(t: T): boolean {
        var len = this._arr.length;
        for (var i = 0; i < len; i++) {
            if (t === this._arr[i]) {
                return false;
            }
        }
        this._arr.push(t);
        return true;
    }

    /**
     * 查询集合中元素的个数。
     * 
     * @returns 元素个数。
     */
    public size(): number {
        return Object.keys(this._arr).length;
    }

    /**
     * 清空集合。
     */
    public clear() {
        delete this._arr;
        this._arr = [];
    }

    /**
     * 把集合转换成队列。
     * 
     * @returns 队列。
     */
    public toArray(): T[] {
        var arr = new Array<T>();
        for (var i = 0; i < this._arr.length; i++) {
            this._arr[i] && arr.push(this._arr[i]);
        }
        return arr;
    }


};